package com.epcs.model.bo;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.epcs.model.dao.EventCategoryDAO;
import com.epcs.model.dao.EventDAO;
import com.epcs.model.dao.FollowingDAO;
import com.epcs.model.dao.NotificationDAO;
import com.epcs.model.dto.Account;
import com.epcs.model.dto.Event;
import com.epcs.model.dto.Eventcategory;
import com.epcs.model.dto.Following;
import com.epcs.model.dto.MostFollowingList;
import com.epcs.model.dto.Notification;
import com.epcs.util.EpcsDateTimeUtil;

public class FollowingBO {
	public List<Following> loadAllNotification(Account account) {
		FollowingDAO following = new FollowingDAO();
		return following.getAllFollowing(account);
	}

	public boolean insertFollowingCategory(Following following) {
		FollowingDAO follow = new FollowingDAO();
		if (follow.insertFollowingToDB(following) != null)
			return true;

		return false;
	}

	public boolean insertFollowingEvent(Following following) {
		FollowingDAO follow = new FollowingDAO();
		if (follow.insertFollowingToDB(following) != null)
			return true;

		return false;
	}

	public boolean followingEventOrCategory(Object obj, Account account) {
		String currentTime = EpcsDateTimeUtil.getCurrentIsoDateTime();
		if (account != null) {
			FollowingDAO followingDAO = new FollowingDAO();
			NotificationDAO notificationDAO = new NotificationDAO();
			Event event = null;
			Eventcategory eventCategory = null;
			String typeOfFollow = "";
			Following following = new Following();

			if (obj instanceof Event) {
				typeOfFollow = "event";
				event = (Event) obj;

				// tạo following
				following.setAccount(account);
				following.setIdOfFollow(event.getEventId());
				following.setTypeOfFollow(typeOfFollow);
				following = followingDAO.insertFollowingToDB(following);


			} else if (obj instanceof Eventcategory) {
				typeOfFollow = "category";
				eventCategory = (Eventcategory) obj;

				following.setAccount(account);
				following.setIdOfFollow(eventCategory.getEventCategoryId());
				following.setTypeOfFollow(typeOfFollow);
				followingDAO.insertFollowingToDB(following);
			}

			return true;
		}
		return false;
	}

	public boolean unfollowingEventOrCategory(Object obj, Account account) {
		if (account != null) {
			FollowingDAO followingDAO = new FollowingDAO();
			NotificationDAO notificationDAO = new NotificationDAO();
			Event event = null;
			Eventcategory eventCategory = null;

			if (obj instanceof Event) {
				event = (Event) obj;

				Following following = followingDAO.loadFollowingEvent(account,
						event.getEventId());

				// lấy following tạo notify -- dạng comment
				List<Notification> listOfNotification = notificationDAO
						.getAllNotification(following);
				if (listOfNotification != null) {
					for (int i = 0; i < listOfNotification.size(); i++) {
						notificationDAO.deleteNotification(listOfNotification
								.get(i));
					}
				}
				if (following != null) {
					followingDAO.deleteFollowingCategorybyAccount(following);
				}

			} else if (obj instanceof Eventcategory) {
				eventCategory = (Eventcategory) obj;

				Following following = followingDAO.loadFollowingCategory(account,
						eventCategory.getEventCategoryId());
				if (following != null) {
					followingDAO.deleteFollowingCategorybyAccount(following);
				}
			}

			return true;
		}
		return false;
	}

	public Following loadFollowing(Account account, int idOfEvent) {
		FollowingDAO follow = new FollowingDAO();
		return follow.loadFollowingEvent(account, idOfEvent);
	}

	public int getNumberOfFollowingByEvent(Event event) {
		FollowingDAO follow = new FollowingDAO();
		return follow.getNumberOfFollowingByEventID(event.getEventId());
	}
	
	
	public List<Object> getNumberOfFollowedCategoryByCategoryIDList(List<Integer> categoryIdList) {
		FollowingDAO followDAO = new FollowingDAO();
		List<Object> objectList = new ArrayList<Object>();
		List<Integer> numberOfFollow = new ArrayList<Integer>();
		for (int i = 0; i< categoryIdList.size(); i++){
			int numberOfFollowing = followDAO.getNumberOfFollowingByCategoryID(categoryIdList.get(i));
			
			numberOfFollow.add(numberOfFollowing);
		}
		
		// sort list lại theo numberOfFollow
		for (int i = 0; i < numberOfFollow.size() - 1; i++){
			for (int j = i + 1; j < numberOfFollow.size(); j++){
				if (numberOfFollow.get(j).compareTo(numberOfFollow.get(i)) > 0){
					
					// sort lại theo numberOfFollow
					Integer temp = numberOfFollow.get(i);
					numberOfFollow.set(i, numberOfFollow.get(j));
					numberOfFollow.set(j, temp);
					
					// kèm theo đó là sort lại cho categoryID list
					temp = categoryIdList.get(i);
					categoryIdList.set(i, categoryIdList.get(j));
					categoryIdList.set(j, temp);
				}
			}
		}
		
		// nhét vào objectList
		objectList.add(categoryIdList);
		objectList.add(numberOfFollow);
				
		return objectList;
	}
	
	public Following loadFollowingEventById(int id) {
		FollowingDAO follow = new FollowingDAO();
		return follow.loadFollowingEventById(id);
	}

	public boolean deleteFollowingCategorybyAccount(Following following) {
		FollowingDAO follow = new FollowingDAO();
		return follow.deleteFollowingCategorybyAccount(following);
	}

	public List<Following> getFollowingByEventID(int eventID) {
		FollowingDAO follow = new FollowingDAO();
		return follow.getFollowingByEventID(eventID);
	}

	public List<Object> getMostFollowingEventList(int pageNumber, int maxRecord, Account account ) {
		List<Object> objectList = new ArrayList<Object>();
		
		FollowingDAO followDAO = new FollowingDAO();
		EventDAO eventDAO =  new EventDAO();
		EventCategoryDAO eventCategoryDAO =  new EventCategoryDAO();
		List<Integer> listCategoryId = followDAO.getCategoryIdListByAccount(account);
		List<Eventcategory> userCategoryList = eventCategoryDAO.getEventCategoryListByCategoryIdList(listCategoryId);
		List<Integer> eventIdList = eventDAO.getEventIdListByUserCategory(userCategoryList,"endTime",null);
		List<MostFollowingList> mostFollowingList = followDAO.getMostFollowingList((pageNumber - 1) * maxRecord, maxRecord, eventIdList);
		
		
		if(mostFollowingList != null){
			
			//nhét objectList
			objectList.add(mostFollowingList);
			//duyệt list eventId
			if (mostFollowingList != null) {
				List<Event> listEvent = new ArrayList<Event>();

				for (int i = 0; i < mostFollowingList.size(); i++) {
					// lấy 1 trong những event được follow nhìu nhất
					Event event = eventDAO.getEventByEventId(mostFollowingList.get(
							i).getIdOfFollow());
					if (event.getDescription().length() > 100) {
						String desc = event.getDescription().substring(0, 100);
						event.setDescription(desc + "...");
					}
					event.setStartTime(EpcsDateTimeUtil.convertToJSPDatetime(event
							.getStartTime()));
					event.setEndTime(EpcsDateTimeUtil.convertToJSPDatetime(event
							.getEndTime()));
					// add event vào list
					listEvent.add(event);
				}
				//nhét objectList
				objectList.add(listEvent);
			}
		}
		
		return objectList;
	}

	public List<Account> getAllAccountFollowEvent(int idOfEvent) {
		FollowingDAO follow = new FollowingDAO();
		return follow.getAllAccountFollowEvent(idOfEvent);
	}

	public List<Following> getFollowingEventByAccount(Account account) {
		FollowingDAO follow = new FollowingDAO();
		return follow.getFollowingEventByAccount(account);
	}

	public List<Following> getFollowingForComment(Account account, int eventID) {
		FollowingDAO follow = new FollowingDAO();
		List<Following> listFollow = follow.getFollowingByEventID(eventID);
		List<Following> outputList = new ArrayList<Following>();
		if (listFollow != null) {
			for (int i = 0; i < listFollow.size(); i++) {
				if (!listFollow.get(i).getAccount().getUsername()
						.equals(account.getUsername())) {
					outputList.add(listFollow.get(i));
				}
			}
		}

		return outputList;
	}

	public List<Following> getFollowingListByEventList(List<Event> eventList,Account account) {
		FollowingBO followBO = new FollowingBO();
		List<Following> listFollowing = new ArrayList<Following>();
		if (eventList != null) {
			for (int i = 0; i < eventList.size(); i++) {
				Event event = eventList.get(i);
				if (event.getDescription().length() > 100) {
					String desc = event.getDescription().substring(0, 100);
					event.setDescription(desc + "...");
				}
				listFollowing.add(followBO.loadFollowing(account,event.getEventId()));
			}
		}
		return listFollowing;
	}
   public List<Integer> getEventIdListByAccount(Account account){
    	FollowingDAO followDAO = new FollowingDAO();
    	return followDAO.getEventIdListByAccount(account);
    }
   public List<Following> getFollowingListByFollowingIdList(List<Integer> followingIdList, Account account) {
	   FollowingDAO followingDAO = new FollowingDAO();
	   return followingDAO.getFollowingList(followingIdList,account);
   }
   public Following loadFollowingEvent(Account account, String idOfEvent) {
		FollowingDAO follow = new FollowingDAO();
		Integer Id;
		try{
			Id = Integer.valueOf(idOfEvent);
		}catch(NumberFormatException ex){
			return null;
		}
		return follow.loadFollowingEvent(account, Id);
	}
}
